<!DOCTYPE html>






<html class="theme-next muse use-motion" lang="zh-Hans">
<head><meta name="generator" content="Hexo 3.9.0">
  <meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
<meta name="theme-color" content="#222">







  <script src="/lib/pace/pace.min.js?v=1.0.2"></script>
  <link href="/lib/pace/pace-theme-minimal.min.css?v=1.0.2" rel="stylesheet">







<meta http-equiv="Cache-Control" content="no-transform">
<meta http-equiv="Cache-Control" content="no-siteapp">


















  <link href="/lib/fancybox/source/jquery.fancybox.css?v=2.1.5" rel="stylesheet" type="text/css">



















































<link href="/lib/font-awesome/css/font-awesome.min.css?v=4.6.2" rel="stylesheet" type="text/css">

<link href="/css/main.css?v=5.1.3" rel="stylesheet" type="text/css">


  <link rel="apple-touch-icon" sizes="180x180" href="/images/apple-touch-icon-next.png?v=5.1.3">


  <link rel="icon" type="image/png" sizes="32x32" href="/images/favicon-32x32-next.png?v=5.1.3">


  <link rel="icon" type="image/png" sizes="16x16" href="/images/favicon-16x16-next.png?v=5.1.3">


  <link rel="mask-icon" href="/images/logo.svg?v=5.1.3" color="#222">





  <meta name="keywords" content="Android, Java">










<meta name="description" content="哈哈~">
<meta name="keywords" content="zachaxy">
<meta property="og:type" content="website">
<meta property="og:title" content="zachaxy">
<meta property="og:url" content="https://zachaxy.github.io/page/6/index.html">
<meta property="og:site_name" content="zachaxy">
<meta property="og:description" content="哈哈~">
<meta property="og:locale" content="zh-Hans">
<meta name="twitter:card" content="summary">
<meta name="twitter:title" content="zachaxy">
<meta name="twitter:description" content="哈哈~">



<script type="text/javascript" id="hexo.configurations">
  var NexT = window.NexT || {};
  var CONFIG = {
    root: '/',
    scheme: 'Muse',
    version: '5.1.3',
    sidebar: {"position":"right","display":"hide","offset":12,"b2t":false,"scrollpercent":true,"onmobile":true},
    fancybox: true,
    tabs: true,
    motion: {"enable":true,"async":false,"transition":{"post_block":"fadeIn","post_header":"slideDownIn","post_body":"slideDownIn","coll_header":"slideLeftIn","sidebar":"slideUpIn"}},
    duoshuo: {
      userId: 'undefined',
      author: '博主'
    },
    algolia: {
      applicationID: '',
      apiKey: '',
      indexName: '',
      hits: {"per_page":10},
      labels: {"input_placeholder":"Search for Posts","hits_empty":"We didn't find any results for the search: ${query}","hits_stats":"${hits} results found in ${time} ms"}
    }
  };
</script>



  <link rel="canonical" href="https://zachaxy.github.io/page/6/">





  <title>zachaxy</title>









</head>

<body itemscope itemtype="http://schema.org/WebPage" lang="zh-Hans">






  <div class="container sidebar-position-right
  page-home">
    <div class="headband"></div>

    <header id="header" class="header" itemscope itemtype="http://schema.org/WPHeader">
      <div class="header-inner"><div class="site-brand-wrapper">
  <div class="site-meta ">


    <div class="custom-logo-site-title">
      <a href="/" class="brand" rel="start">
        <span class="logo-line-before"><i></i></span>
        <span class="site-title">zachaxy</span>
        <span class="logo-line-after"><i></i></span>
      </a>
    </div>

        <h1 class="site-subtitle" itemprop="description">纵情向前！</h1>

  </div>

  <div class="site-nav-toggle">
    <button>
      <span class="btn-bar"></span>
      <span class="btn-bar"></span>
      <span class="btn-bar"></span>
    </button>
  </div>
</div>

<nav class="site-nav">



    <ul id="menu" class="menu">


        <li class="menu-item menu-item-home">
          <a href="/" rel="section">

              <i class="menu-item-icon fa fa-fw fa-home"></i> <br>

            首页
          </a>
        </li>


        <li class="menu-item menu-item-tags">
          <a href="/tags" rel="section">

              <i class="menu-item-icon fa fa-fw fa-tags"></i> <br>

            标签
          </a>
        </li>


        <li class="menu-item menu-item-archives">
          <a href="/archives" rel="section">

              <i class="menu-item-icon fa fa-fw fa-archive"></i> <br>

            归档
          </a>
        </li>


        <li class="menu-item menu-item-about">
          <a href="/about" rel="section">

              <i class="menu-item-icon fa fa-fw fa-user"></i> <br>

            关于
          </a>
        </li>



        <li class="menu-item menu-item-search">

            <a href="javascript:;" class="popup-trigger">


              <i class="menu-item-icon fa fa-search fa-fw"></i> <br>

            搜索
          </a>
        </li>

    </ul>



    <div class="site-search">

  <div class="popup search-popup local-search-popup">
  <div class="local-search-header clearfix">
    <span class="search-icon">
      <i class="fa fa-search"></i>
    </span>
    <span class="popup-btn-close">
      <i class="fa fa-times-circle"></i>
    </span>
    <div class="local-search-input-wrapper">
      <input autocomplete="off" placeholder="搜索..." spellcheck="false" type="text" id="local-search-input">
    </div>
  </div>
  <div id="local-search-result"></div>
</div>



    </div>

</nav>



 </div>
    </header>

    <main id="main" class="main">
      <div class="main-inner">
        <div class="content-wrap">
          <div id="content" class="content">

  <section id="posts" class="posts-expand">









  <article class="post post-type-normal" itemscope itemtype="http://schema.org/Article">



  <div class="post-block">
    <link itemprop="mainEntityOfPage" href="https://zachaxy.github.io/2017/12/05/Groovy-相对-Java-的一些新玩意/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="name" content="zachaxy">
      <meta itemprop="description" content>
      <meta itemprop="image" content="/images/avatar.jpg">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="zachaxy">
    </span>


      <header class="post-header">



          <h2 class="post-title" itemprop="name headline">

                <a class="post-title-link" href="/2017/12/05/Groovy-相对-Java-的一些新玩意/" itemprop="url">Groovy 相对 Java 的一些新玩意</a></h2>


        <div class="post-meta">
          <span class="post-time">

              <span class="post-meta-item-icon">
                <i class="fa fa-calendar-o"></i>
              </span>

                <span class="post-meta-item-text">发表于</span>

              <time title="创建于" itemprop="dateCreated datePublished" datetime="2017-12-05T20:03:55+08:00">
                2017-12-05
              </time>





          </span>













            <div class="post-wordcount">


                <span class="post-meta-item-icon">
                  <i class="fa fa-file-word-o"></i>
                </span>

                  <span class="post-meta-item-text">字数统计&#58;</span>

                <span title="字数统计">
                  2,155
                </span>





            </div>




        </div>
      </header>





    <div class="post-body" itemprop="articleBody">






          <h1 id="Groovy-是轻量级的-Java"><a href="#Groovy-是轻量级的-Java" class="headerlink" title="Groovy 是轻量级的 Java"></a>Groovy 是轻量级的 Java</h1><ul>
<li>方法，闭包中 return 语句是可选的，如果没有 return，则默认返回方法、闭包的最后一条语句的值</li>
<li>方法和类默认的修饰符都是 public</li>
<li>Groovy 不强迫我们捕获自己不关系的异常，这些异常会被传递给方法的调用者</li>
<li>静态方法中也可以使用 this 来引用当前的静态类 Class 对象。</li>
<li>提供安全导航操作符 <code>.?</code> 来避免对象非空的判断
          <!--noindex-->
          <div class="post-button text-center">
            <a class="btn" href="/2017/12/05/Groovy-相对-Java-的一些新玩意/#more" rel="contents">
              阅读全文 &raquo;
            </a>
          </div>
          <!--/noindex-->


    </li></ul></div>










    <footer class="post-footer">








        <div class="post-eof"></div>

    </footer>
  </div>



  </article>











  <article class="post post-type-normal" itemscope itemtype="http://schema.org/Article">



  <div class="post-block">
    <link itemprop="mainEntityOfPage" href="https://zachaxy.github.io/2017/12/05/hexo搭建改良/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="name" content="zachaxy">
      <meta itemprop="description" content>
      <meta itemprop="image" content="/images/avatar.jpg">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="zachaxy">
    </span>


      <header class="post-header">



          <h2 class="post-title" itemprop="name headline">

                <a class="post-title-link" href="/2017/12/05/hexo搭建改良/" itemprop="url">hexo搭建改良</a></h2>


        <div class="post-meta">
          <span class="post-time">

              <span class="post-meta-item-icon">
                <i class="fa fa-calendar-o"></i>
              </span>

                <span class="post-meta-item-text">发表于</span>

              <time title="创建于" itemprop="dateCreated datePublished" datetime="2017-12-05T19:20:39+08:00">
                2017-12-05
              </time>





          </span>













            <div class="post-wordcount">


                <span class="post-meta-item-icon">
                  <i class="fa fa-file-word-o"></i>
                </span>

                  <span class="post-meta-item-text">字数统计&#58;</span>

                <span title="字数统计">
                  3,683
                </span>





            </div>




        </div>
      </header>





    <div class="post-body" itemprop="articleBody">






          <p>hexo 搭建改良<br>之前使用<a href="https://zachaxy.github.io/2017/03/30/hexo%E6%90%AD%E5%BB%BA%E5%8D%9A%E5%AE%A2%E8%BF%87%E7%A8%8B%E5%85%A8%E7%BA%AA%E5%BD%95/">hexo 搭建博客过程全纪录</a>已经可以成功的搭建一个 hexo 的博客了，使用了一段时间之后，发现了一个问题，就是博客只能在当前的这台 pc 上发布，但是有时候想在家也写写博客并立即发布，之前的博客只能基于单终端的发布。因此在多个端上进行 hexo 的同步成为当前需要解决的问题，为此，我这里进行了三次改进。通过不断的改良，也使我对 hexo 有了进一步的了解。</p>
          <!--noindex-->
          <div class="post-button text-center">
            <a class="btn" href="/2017/12/05/hexo搭建改良/#more" rel="contents">
              阅读全文 &raquo;
            </a>
          </div>
          <!--/noindex-->


    </div>










    <footer class="post-footer">








        <div class="post-eof"></div>

    </footer>
  </div>



  </article>











  <article class="post post-type-normal" itemscope itemtype="http://schema.org/Article">



  <div class="post-block">
    <link itemprop="mainEntityOfPage" href="https://zachaxy.github.io/2017/11/13/Mac快速上手/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="name" content="zachaxy">
      <meta itemprop="description" content>
      <meta itemprop="image" content="/images/avatar.jpg">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="zachaxy">
    </span>


      <header class="post-header">



          <h2 class="post-title" itemprop="name headline">

                <a class="post-title-link" href="/2017/11/13/Mac快速上手/" itemprop="url">Mac快速上手</a></h2>


        <div class="post-meta">
          <span class="post-time">

              <span class="post-meta-item-icon">
                <i class="fa fa-calendar-o"></i>
              </span>

                <span class="post-meta-item-text">发表于</span>

              <time title="创建于" itemprop="dateCreated datePublished" datetime="2017-11-13T19:20:59+08:00">
                2017-11-13
              </time>





          </span>













            <div class="post-wordcount">


                <span class="post-meta-item-icon">
                  <i class="fa fa-file-word-o"></i>
                </span>

                  <span class="post-meta-item-text">字数统计&#58;</span>

                <span title="字数统计">
                  4,874
                </span>





            </div>




        </div>
      </header>





    <div class="post-body" itemprop="articleBody">







            <h1 id="基本快捷键"><a href="#基本快捷键" class="headerlink" title="基本快捷键"></a>基本快捷键</h1><h2 id="映射关系"><a href="#映射关系" class="headerlink" title="映射关系"></a>映射关系</h2><p>在看一些软件提供的快捷键时，都是给出如下的字符，其与键盘上的按键对应关系如下：</p>
<ul>
<li>⌘ (command)</li>
<li>⌥ (option)</li>
<li>⇧ (shift)</li>
<li>⌃ (control)</li>
<li>⌫ (delete)</li>
</ul>
<h2 id="MacOS-基本快捷键"><a href="#MacOS-基本快捷键" class="headerlink" title="MacOS 基本快捷键"></a>MacOS 基本快捷键</h2><p>当你熟记了这 4 个符号之后，那么就来记一些常用的快捷键吧：</p>
<ul>
<li><code>⌘ + tab</code> 切换应用程序</li>
<li><code>⌘ + ⌫</code> 将选中的文件移动到废纸篓</li>
<li><code>⌘ + c</code> 拷贝</li>
<li><code>⌘ + v</code> 粘贴</li>
<li><code>⌘ + ⌥ + v</code> 移动文件</li>
<li><code>⌘ + q</code> 退出当前应用</li>
<li><code>⌘ + h</code> 隐藏当前窗口</li>
<li><code>⌘ + m</code> 最小化当前窗口</li>
<li><code>⌘ + w</code> 关闭当前窗口</li>
<li><code>⌘ + &lt;-</code> 移动到行首，类 win 下的 home</li>
<li><code>⌘ + -&gt;</code> 移动到行末，类 win 下的 end</li>
<li><code>⌘ + delete</code>删除光标之前整行内容/选中文件的话，会将该文件移动到废纸篓(删除文件的功能更常用)</li>
<li><code>fn + delete</code>删除光标之后的一个字符；</li>
<li><code>⌥ + delete</code> 删除光标之前的一个单词（英文有效）；</li>
</ul>
<ul>
<li><code>⌘ + ⌥ + Esc</code> 类似 win 下的任务管理器，用来强制关闭应用</li>
</ul>
<p>休眠、关机</p>
<ul>
<li>休眠快捷键:<code>ctrl + shift + 右上角</code></li>
<li>关机快捷键:<code>cmd + opt + 右上角</code></li>
</ul>
<p>最近常用的系统快捷键：</p>
<ul>
<li><code>⌘ + 空格</code> 打开 spotlight</li>
<li><code>⌥ + 空格</code> 打开 iterm2</li>
<li><code>⌃ + 空格</code> 中英文输入源切换；不知道为什么，搜狗输入法和系统自带英文输入法会非人为切换，这是要切换回来就用该快捷键</li>
</ul>
<h1 id="显示隐藏文件"><a href="#显示隐藏文件" class="headerlink" title="显示隐藏文件"></a>显示隐藏文件</h1><p><code>Command+Shift+.</code> 可以显示隐藏文件、文件夹，再按一次，恢复隐藏；但是这个方法是有版本限制的，目前在10.11上用不了;可能12上有用。</p>
<p>另一种可行的方法命令行执行显示隐藏文件：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">defaults write com.apple.finder AppleShowAllFiles -bool true;</span><br><span class="line">KillAll Finder</span><br></pre></td></tr></table></figure>

<p>不显示,将上面的 true 改为 false 即可。</p>
<h2 id="解决-IDE-中配置环境变量的问题"><a href="#解决-IDE-中配置环境变量的问题" class="headerlink" title="解决 IDE 中配置环境变量的问题"></a>解决 IDE 中配置环境变量的问题</h2><p>很多 IDE 需要制定 SDK 的位置。例如使用 Intellj Idea开发 Groovy，就需要配置其 GROOVY 的路径，可是其路径安装时被放在了一个隐藏路径下，而在 ide 中选择路径时，是无法显示隐藏路径的。<br>解决方法：finder下使用Command+Shift+G 可以前往任何文件夹，包括隐藏文件夹。这时将隐藏的路径<strong>拖到</strong>左边的快速导航，然后在IDE 中选择路径，点击左侧的快速导航即可。</p>
<h1 id="homebrew"><a href="#homebrew" class="headerlink" title="homebrew"></a>homebrew</h1><h2 id="简介"><a href="#简介" class="headerlink" title="简介"></a>简介</h2><p>mac os 中的软件包管理器，类似 CentOS 中的 yum，Ubuntu 中的 apt-get。<br>安装方式：在终端中输入：<code>/usr/bin/ruby -e &quot;$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)&quot;</code></p>
<p>接下来就可以想 yum 那样在 macOS 中使用 brew 命令来安装软件了；</p>
<p>Homebrew 会将软件包安装到独立目录(默认：/usr/local/Cellar)，并将可执行文件软链接至 /usr/local/bin</p>
<h2 id="常用命令"><a href="#常用命令" class="headerlink" title="常用命令"></a>常用命令</h2><ul>
<li>brew search xxx：在软件仓库中搜索 xxx 软件，支持正则搜索</li>
<li>brew install xxx：安装 xxx 软件</li>
<li>brew uninstall xxx：卸载 xxx 软件，前提是使用 brew install 安装过的，其它方式不行；</li>
<li>brew info xxx:显示 xxx 软件的版本信息，安装路径，依赖信息等；</li>
<li>brew deps xxx：显示 xxx 软件的依赖；</li>
</ul>
<ul>
<li>brew list：查看使用 brew install 安装过的软件</li>
<li>brew update：更新 homebrew，但是没有必要单独执行这个命令，我们每次在执行 brew install 的时候，都会先执行 brew update</li>
</ul>
<h1 id="sdkman"><a href="#sdkman" class="headerlink" title="sdkman"></a>sdkman</h1><p>之前在学习 groovy 的时候,查看groovy 的官网，其推荐的安装方式是先安装 sdkman， 然后通过 sdk man 来安装 groovy。<br>sdkman 和前面介绍的 homebrew 有些类似，都是软件管理工具。而与 homebrew 不同的是，sdkman 不仅可以方便的安装软件，同时还可以管理多个开发工具版本之间的切换，eg：python2.x 和 python3.x，用 sdkman 就能很好的解决。<br>其安装方式：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">curl -s get.sdkman.io | bash</span><br><span class="line">source &quot;$HOME/.sdkman/bin/sdkman-init.sh&quot;</span><br></pre></td></tr></table></figure>

<p>第一步是安装，第二步是将 sdkman 配置到环境变量中，因为我使用的是 zsh，所以其自动写到了 <code>.zshrc</code>文件中。<br>最后其安装软件的方式也很简单，这里以安装 <strong>GROOVY</strong> 为例</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">sdk install groovy</span><br></pre></td></tr></table></figure>

<p>其所下载的软件被放到了<code>/Users/用户名/.sdkman/candidates/</code></p>
<p>其安装软件的方式和 homebrew 是类似的，只需一个命令即可安装。<br>当然其强大的地方还在于可以管理多个软件的版本，具体使用请参考<a href="http://sdkman.io/usage.html" target="_blank" rel="noopener">官网</a></p>
<h1 id="sublime"><a href="#sublime" class="headerlink" title="sublime"></a>sublime</h1><p>目前最常用的快捷键：</p>
<ul>
<li>⌘ + c 复制当前行</li>
<li>⌘ + v 粘贴当前行</li>
<li>⌘ + x 剪切当前行</li>
<li>shift + ⌘ + &lt;-:选中光标到行首的所有字符</li>
<li>shift + ⌘ + -&gt;:选中光标到行首的所有字符</li>
<li>shift + ⌥ + &lt;-:选中光标到行首的一个单词</li>
<li>shift + ⌥ + -&gt;:选中光标到行首的一个单词</li>
</ul>
<ul>
<li>⌘ + d：高亮下一个选中的单词</li>
<li>⌘ + ctrl + g:高亮选中的所有单词</li>
<li>⌘ + ⌥ ：矩形区域选择</li>
<li>⌘ + shift + v (Win: Ctrl-Shift-v) 进行自适应缩进的粘贴</li>
</ul>
<ul>
<li><p>⌘ + enter 另起一行</p>
</li>
<li><p>⌘ + ⌃ 上下行切换</p>
</li>
<li><p>⌘ + ⇧ + p 命令提示</p>
</li>
<li><p>⌘ + ⌃ + p 切换工程</p>
</li>
</ul>
<h2 id="插件安装"><a href="#插件安装" class="headerlink" title="插件安装"></a>插件安装</h2><p>首先要安装的是 Package Control 插件，它是一个方便 Sublime text 管理插件的插件。<br>从菜单 View -&gt; Show Console 或者 <code>ctrl + ~</code> 快捷键，调出 console。将以下 Python 代码粘贴进去并 enter 执行(注：针对的是 sublime3)</p>
<figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> urllib.request,os; pf = <span class="string">'Package Control.sublime-package'</span>; ipp = sublime.installed_packages_path(); urllib.request.install_opener( urllib.request.build_opener( urllib.request.ProxyHandler()) ); open(os.path.join(ipp, pf), <span class="string">'wb'</span>).write(urllib.request.urlopen( <span class="string">'http://sublime.wbond.net/'</span> + pf.replace(<span class="string">' '</span>,<span class="string">'%20'</span>)).read())</span><br></pre></td></tr></table></figure>

<p>接下来再安装插件就可以通过 Package Control 来安装了，快捷键 <code>Ctrl+Shift+P</code>（菜单 – &gt;Tools –&gt; Command Paletter），输入 install 选中Install Package并回车,然后输入想要安装的插件名称即可，支持模糊搜索。</p>
<p>插件推荐如下：</p>
<ul>
<li>Alignment：代码对齐插件</li>
<li>BracketHilight：括号配对显示</li>
<li>DocBlockr：注释块</li>
<li>SublimeLinter：代码检查，还需要和具体的语言插件配对才可以使用eg:SublimeLinter-javac 使用，最好还是用编译器写代码。。</li>
<li>SideBarEnhancements：mac 下的名称，win 下叫 sidebar，提供了侧边连的增强功能；</li>
</ul>
<h2 id="主题配置"><a href="#主题配置" class="headerlink" title="主题配置"></a>主题配置</h2><p>主题的安装同插件一样，在 Package Control 中直接搜索即可。目前用的 <code>Material Theme</code></p>
<h2 id="个人配置"><a href="#个人配置" class="headerlink" title="个人配置"></a>个人配置</h2><figure class="highlight json"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br></pre></td><td class="code"><pre><span class="line">&#123;</span><br><span class="line">	<span class="attr">"always_show_minimap_viewport"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"bold_folder_labels"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"color_scheme"</span>: <span class="string">"Packages/Material Theme/schemes/Material-Theme.tmTheme"</span>,</span><br><span class="line">	<span class="attr">"draw_white_space"</span>: <span class="string">"all"</span>,</span><br><span class="line">	<span class="attr">"font_size"</span>: <span class="number">15</span>,</span><br><span class="line">	<span class="attr">"highlight_line"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"ignored_packages"</span>:</span><br><span class="line">	[</span><br><span class="line">		<span class="string">"Vintage"</span></span><br><span class="line">	],</span><br><span class="line">	<span class="attr">"indent_guide_options"</span>:</span><br><span class="line">	[</span><br><span class="line">		<span class="string">"draw_normal"</span>,</span><br><span class="line">		<span class="string">"draw_active"</span></span><br><span class="line">	],</span><br><span class="line">	<span class="attr">"overlay_scroll_bars"</span>: <span class="string">"enabled"</span>,</span><br><span class="line">	<span class="attr">"rulers"</span>:</span><br><span class="line">	[</span><br><span class="line">		<span class="number">100</span></span><br><span class="line">	],</span><br><span class="line">	<span class="attr">"save_on_focus_lost"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"scroll_past_end"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"show_encoding"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"show_full_path"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"show_line_endings"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"spell_check"</span>: <span class="literal">false</span>,</span><br><span class="line">	<span class="attr">"tab_size"</span>: <span class="number">4</span>,</span><br><span class="line">	<span class="attr">"theme"</span>: <span class="string">"Material-Theme.sublime-theme"</span>,</span><br><span class="line">	<span class="attr">"trim_trailing_white_space_on_save"</span>: <span class="literal">true</span>,</span><br><span class="line">	<span class="attr">"update_check"</span>: <span class="literal">false</span>,</span><br><span class="line">	<span class="attr">"word_wrap"</span>: <span class="literal">true</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<h2 id="project-管理功能"><a href="#project-管理功能" class="headerlink" title="project 管理功能"></a>project 管理功能</h2><p>sublime 提供了像 IDE 那样基于 project 的功能，用来管理一组文件夹。只要保存为 project，那么下次再打开该 project 时，就会恢复上次打开的文件。这个功能在平时的工作中非常实用。</p>
<p>打开 sublime，注意此时 sublime 的窗口中不能有其它文件，否则一会儿保存为 project 时会将当前窗口的所有文件一块存入 project，然而 sublime 默认打开是会将上次关闭前打开的文件都打开的。所以，如果想单独创建一个 project，可以通过<code>cmd + shift + n</code>(win 下快捷键为：<code>ctrl + shift + n</code>) 重新打开一个窗口，此时再将想要打开的文件夹拖入当前窗口，或者用 <code>project -&gt; Add Folder to Project</code> 选择文件夹。同时我们在一个 project 中可以打开多个(不同路径)文件夹，然后选择 <code>Project -&gt; Save Project As...</code> 自定义该 project 的名字和保存路径，此时会在保存路径下生成两个文件，分别为<code>.workspace</code>和<code>.project</code>。前者文件中保存的是当前窗口已经打开的文件，这样下次打开该 project 时还会恢复。后者保存的是当前 project 中的所有文件的路径，前面也说了 sublime 中的 project 中可以添加多个文件夹进来。</p>
<p>tips：</p>
<ol>
<li>project 文件最好集中保存到一个特定的目录下，这样方便统一管理。</li>
<li>基于上一点，每次保存 project 时，都要选择指定的保存路径，所以推荐<code>project manager</code>的插件，在配置文件中指定路径，这样就免去每次保存 project 时选择路径的麻烦。</li>
<li>多个 project 的快速切换<code>cmd + ctrl + p</code>（win 下快捷键为：<code>ctrl + alt + p</code>），选择要切换的 project，这样的话当前窗口就会被替换为目标 project。如果你想打开多个 project，那么就用<code>cmd + shift + n</code>打开一个新的窗口，再用<code>cmd + ctrl + p</code>打开新的 project 即可。</li>
</ol>
<p>project manager 的插件的使用<br>在安装了该插件之后，首先要在该插件的配置文件中配置 project 保存的路径。在新建项目时，打开一个空白窗口，向其中拖入文件夹，然后使用<code>cmd + shift + p</code>打开命令行，输入<code>pm</code>，选择<code>Add New Project</code>，此时会在 sublime 底部弹出文本框，输入 project 的名字，那么该 project 就会被保存到之前配置的路径中。</p>
<h1 id="Iterm2-的使用"><a href="#Iterm2-的使用" class="headerlink" title="Iterm2 的使用"></a>Iterm2 的使用</h1><p>Iterm2 与系统自带的 terminal 类似，但是其功能更为强大；</p>
<h2 id="基本快捷键-1"><a href="#基本快捷键-1" class="headerlink" title="基本快捷键"></a>基本快捷键</h2><p>编辑相关：(注意和光标移动相关的操作全是 ctrl 打头的)</p>
<ul>
<li>清除当前行：ctrl + u</li>
<li>到行首：ctrl + a</li>
<li>到行尾：ctrl + e</li>
<li>删除光标之前的单词：ctrl + w</li>
<li>删除到文本末尾：ctrl + k</li>
<li>清屏：ctrl + l 或者 command + r</li>
</ul>
<p>编辑中不太常用的：</p>
<ul>
<li>搜索命令历史：ctrl + r (类似于 history | grep xxx，搜索之前执行过的命令)</li>
<li>前进后退：ctrl + f/b (相当于左右方向键)</li>
<li>上一条命令：ctrl + p</li>
<li>交换光标处文本：ctrl + t</li>
</ul>
<p>历史记录：</p>
<ul>
<li>查看历史命令：<code>command + ;</code>(输入若干字符，弹出自动补齐窗口，列出曾经使用过的命令)</li>
<li>查看剪贴板历史：command + shift + h</li>
</ul>
<p>标签相关：</p>
<ul>
<li>新建标签：command + t</li>
<li>关闭标签：command + w</li>
<li>切换标签：command + 数字 command + 左右方向键</li>
<li>切换全屏：command + enter</li>
<li>查找：command + f</li>
</ul>
<p>分屏相关：(使用频率较低)</p>
<ul>
<li>垂直分屏：command + d</li>
<li>水平分屏：command + shift + d</li>
<li>切换屏幕：command + option + 方向键 command + [ 或 command + ]</li>
</ul>
<h2 id="全局呼出"><a href="#全局呼出" class="headerlink" title="全局呼出"></a>全局呼出</h2><p>默认是 <code>option + 空格</code><br>修改方法是在 preference-&gt;keys-&gt;hot key 勾选，并设置；<br>将快捷键改为 command + command，也是个不错的选择；</p>
<h2 id="智能选中"><a href="#智能选中" class="headerlink" title="智能选中"></a>智能选中</h2><p>在 iTerm2 中，双击选中，三击选中整行，四击智能选中（智能规则可配置），可以识别网址，引号引起的字符串，邮箱地址等。（很多时候双击的选中就已经很智能了）<br>在 iTerm2 中，选中即复制。即任何选中状态的字符串都被放到了系统剪切板中。</p>
<h2 id="巧用-Command-键"><a href="#巧用-Command-键" class="headerlink" title="巧用 Command 键"></a>巧用 Command 键</h2><p>按住⌘键:</p>
<ul>
<li>可以拖拽选中的字符串；</li>
<li>点击 url：调用默认浏览器访问该网址；</li>
<li>点击文件：调用默认程序打开文件；</li>
<li>如果文件名是filename:42，且默认文本编辑器是 Macvim、Textmate或BBEdit，将会直接打开到这一行；</li>
<li>点击文件夹：在 finder 中打开该文件夹；</li>
<li>同时按住option键，可以以矩形选中，类似于vim中的ctrl v操作。</li>
</ul>
<h2 id="高亮当前光标："><a href="#高亮当前光标：" class="headerlink" title="高亮当前光标："></a>高亮当前光标：</h2><p><code>⌘ + /</code> :如果一个标签页中开的窗口太多，有时候会找不到当前的鼠标，找到它。</p>
<h2 id="移动光标快捷键修改"><a href="#移动光标快捷键修改" class="headerlink" title="移动光标快捷键修改"></a>移动光标快捷键修改</h2><p>之前的命令单词的移动都是使用 <code>opt + -&gt;</code> / <code>opt +  &lt;-</code> 来实现的,但是这个要在 iterm2 中进行修改,具体修改方式:</p>
<ol>
<li>打开iTerm2的Preferences设置</li>
<li>选择相应的Profile（默认为Default），选择“Keys”选项卡</li>
<li>在Key Mappings看到<code>option+←</code> 和 <code>option+→</code>这两组快捷键用作了其他功能，这里我们分别修改为: 选择Action为“Send Escape Sequence”，然后输入“b”和“f”即可</li>
</ol>
<h1 id="zsh"><a href="#zsh" class="headerlink" title="zsh"></a>zsh</h1><p>终极 shell —— zsh</p>
<h2 id="切换为-zsh"><a href="#切换为-zsh" class="headerlink" title="切换为 zsh"></a>切换为 zsh</h2><p>通过 <code>cat /etc/shells</code> 查看系统自带的 shell，有如下几个：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">/bin/bash</span><br><span class="line">/bin/csh</span><br><span class="line">/bin/ksh</span><br><span class="line">/bin/sh</span><br><span class="line">/bin/tcsh</span><br><span class="line">/bin/zsh</span><br></pre></td></tr></table></figure>

<p>目前系统默认使用的是 bash，接下来使用 <code>chsh -s /bin/zsh</code>将默认的 bash 切换为 zsh，当然想换回默认的 bash，只需键入 <code>chsh -s /bin/bash</code></p>
<p>zsh 的配置主要集中在用户当前目录的.zshrc里，我们对 zsh 的配置都在这个文件中，注意每当我们修改了该配置文件中的内容，都要用 <em>source ~/.zshrc</em>，使配置生效！</p>
<h2 id="安装-Oh-My-ZSH"><a href="#安装-Oh-My-ZSH" class="headerlink" title="安装 Oh My ZSH"></a>安装 Oh My ZSH</h2><p>zsh 相比于 bash 有很强的扩展性，但是其配置过于复杂，于是就有了 Oh My ZSH 来帮助我们简化 zsh 的配置</p>
<p>安装过程也很简单：<br><code>sh -c &quot;$(curl -fsSL https://raw.githubusercontent.com/robbyrussell/oh-my-zsh/master/tools/install.sh)&quot;</code></p>
<p>其被安装到了 <code>/Users/zachaxy/.oh-my-zsh</code></p>
<p>现在整个 shell 的配置文件是 ~/.zshrc,所有的环境变量都在这里改动；</p>
<h2 id="alias-重命名功能"><a href="#alias-重命名功能" class="headerlink" title="alias 重命名功能"></a>alias 重命名功能</h2><p>例如我们为 sublime 添加一个 subl 的命令行，因为 sublime 本身就在其 bin 目录下有一个 subl 的可执行文件，所以直接拿来用就可以，在 zshrc 配置文件添加如下：<br>alias subl=”Applications/Sublime Text.app/Contents/SharedSupport/bin/subl”</p>
<p>然后执行：source .zshrc 是配置生效<br>接下来执行：subl xxx 就会创建并打开一个 xxx 文件；</p>
<h2 id="zsh-配置插件"><a href="#zsh-配置插件" class="headerlink" title="zsh 配置插件"></a>zsh 配置插件</h2><p>打开 ~/.zshrc 配置文件,找到 plugins 的配置，在括号里填入我们想要的插件就可以，可供选择的插件可以在 ~/.oh-my-zsh/plugins,其具体功能可以参考其 github 上的 <a href="https://github.com/robbyrussell/oh-my-zsh/tree/master/plugins" target="_blank" rel="noopener">readme 说明</a></p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">plugins=(</span><br><span class="line">  git</span><br><span class="line">  autojump</span><br><span class="line">  extract</span><br><span class="line">  sublime</span><br><span class="line">)</span><br></pre></td></tr></table></figure>

<p>这里推荐几个可能用的到的插件，注意插件安装的越多，iterm2启动越慢!</p>
<p>插件推荐：</p>
<ul>
<li><p>git：默认自带，主要是 alias 一些 git 的命令</p>
</li>
<li><p>sublime：提供打开文件夹功能，常用命令有：st</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">If st command is called without an argument, launch Sublime Text</span><br><span class="line"></span><br><span class="line">If st is passed a directory, cd to it and open it in Sublime Text</span><br><span class="line"></span><br><span class="line">If st is passed a file, open it in Sublime Text</span><br><span class="line"></span><br><span class="line">If stt command is called, it is equivalent to st ., opening the current folder in Sublime Text</span><br><span class="line"></span><br><span class="line">If sst command is called, it is like sudo st, opening the file or folder in Sublime Text. Useful for editing system protected files.</span><br><span class="line"></span><br><span class="line">If stp command is called, it find a .sublime-project file by traversing up the directory structure. If there is no .sublime-project file, but if the current folder is a Git repo, opens up the root directory of the repo. If the current folder is not a Git repo, then opens up the current directory.</span><br></pre></td></tr></table></figure>
</li>
<li><p>extract：功能强大的解压插件，所有类型的文件解压一个命令x全搞定，再也不需要去记tar后面到底是哪几个参数了。</p>
</li>
<li><p>web-search：命令行：google Android,就会打开浏览器，并用 Google 搜索 Android；(本机 ip暂时不稳定，暂不设置)</p>
</li>
<li><p>wd：快捷文件夹，以后会用到吧；</p>
</li>
<li><p>autojump：必选插件,快速进入某一文件夹。</p>
<p>需要先下载，通过 <code>brew install autojump</code>，然后在 <code>~/.zshrc</code>的最后添加如下指令，  <code>[[ -s $(brew --prefix)/etc/profile.d/autojump.sh ]] &amp;&amp; . $(brew --prefix)/etc/profile.d/autojump.sh</code> ，同时在 plugins 中填入 autojump 插件，这样 autojump 就可以用了，用法：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">首先，要在 zsh 中进入过某一目录 eg：xxx，这样 autojump 就会在自身的数据库中缓存结果，等下次再进入的话，只需要键入 j xxx，在按下 tab 键列出可选目标，然后在通过 tab 选择对应目录,xxx 支持正则，如果之前进入过多个不同位置但是名字相同的文件夹xxx，那么不同 xxx 在数据库中有一个优先级。  可以使用 autojump -h 来查看所有权重，设置权重，清除数据库等；</span><br></pre></td></tr></table></figure>

</li>
</ul>
<h2 id="zsh-主题配置"><a href="#zsh-主题配置" class="headerlink" title="zsh 主题配置"></a>zsh 主题配置</h2><p>同样是在 <code>~/.zshrc</code> 中，找到 <code>ZSH_THEME=&quot;robbyrussell&quot;</code>，在这里配置主题，默认的是 robbyrussell，当然可以换成别的，其它可选的主题都在 <code>~/.oh-my-zsh/themes</code>,<a href="https://github.com/robbyrussell/oh-my-zsh/wiki/Themes" target="_blank" rel="noopener">预览样式</a></p>
<p>这里挑几个较好的主题：</p>
<ul>
<li>blinks</li>
<li>gentoo</li>
<li>gianu</li>
<li>muse</li>
<li>pygmalion</li>
<li>ys</li>
</ul>
<p>最后修改配置，不要忘记执行： <code>source ~/.zshrc</code>，使配置生效</p>
<h1 id="vim-配置"><a href="#vim-配置" class="headerlink" title="vim 配置"></a>vim 配置</h1><p>很多时候查看配置文件，会使用 vim，其实上面介绍的 sublime 也很好用，不过有的人还是习惯用 vim，那么简单介绍一下 vim 的相关配置。</p>
<ol>
<li><code>cp /usr/share/vim/vimrc ~/.vimrc</code>,先复制一份vim配置模板到个人目录下，这样就使得仅对当前用户有效</li>
<li>编辑<code>~/.vimrc</code>，加入 <code>set nu!</code> 显示行号</li>
</ol>
<p>附其它常用配置：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line">set nocompatible                 &quot;去掉有关vi一致性模式，避免以前版本的bug和局限</span><br><span class="line">set nu!                                    &quot;显示行号</span><br><span class="line">set guifont=Luxi/ Mono/ 9   &quot; 设置字体，字体名称和字号</span><br><span class="line">filetype on                              &quot;检测文件的类型</span><br><span class="line">set history=1000                  &quot;记录历史的行数</span><br><span class="line">set background=dark          &quot;背景使用黑色</span><br><span class="line">syntax on                                &quot;语法高亮度显示</span><br><span class="line">set autoindent                       &quot;vim使用自动对齐，也就是把当前行的对齐格式应用到下一行(自动缩进）</span><br><span class="line">set cindent                             &quot;（cindent是特别针对 C语言语法自动缩进）</span><br><span class="line">set smartindent                    &quot;依据上面的对齐格式，智能的选择对齐方式，对于类似C语言编写上有用</span><br><span class="line">set tabstop=4                        &quot;设置tab键为4个空格，</span><br><span class="line">set shiftwidth =4                   &quot;设置当行之间交错时使用4个空格</span><br><span class="line">set ai!                                      &quot; 设置自动缩进</span><br><span class="line">set showmatch                     &quot;设置匹配模式，类似当输入一个左括号时会匹配相应的右括号</span><br><span class="line">set guioptions-=T                 &quot;去除vim的GUI版本中得toolbar</span><br><span class="line">set vb t_vb=                            &quot;当vim进行编辑时，如果命令错误，会发出警报，该设置去掉警报</span><br><span class="line">set ruler                                  &quot;在编辑过程中，在右下角显示光标位置的状态行</span><br><span class="line">set nohls                                &quot;默认情况下，寻找匹配是高亮度显示，该设置关闭高亮显示</span><br><span class="line">set incsearch    &quot;在程序中查询一单词，自动匹配单词的位置；如查询desk单词，当输到/d时，会自动找到第一个d开头的单词，当输入到/de时，会自动找到第一个以ds开头的单词，以此类推，进行查找；当找到要匹配的单词时，别忘记回车</span><br><span class="line">set backspace=2           &quot; 设置退格键可用</span><br></pre></td></tr></table></figure>

<p>其实 zsh 已经把很多参数默认改好了，包括颜色方案啥的，很多都可以用设置的，直接用就行了</p>
<h1 id="Java-环境配置"><a href="#Java-环境配置" class="headerlink" title="Java 环境配置"></a>Java 环境配置</h1><p><a href="http://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html" target="_blank" rel="noopener">下载地址</a>找到MacOS 的安装包，直接双击安装即可。<br>安装之后，不需要配置 Java 环境变量，直接在命令行就可以使用 Java 了，其安装位置是在：<code>/Library/Java/JavaVirtualMachines/</code>，同时系统也为刚刚的安装的 JDK 创建了软连接：<code>/usr/libexec/java_home</code>，也正是因为这个软连接，我们才可以在命令行中直接使用 Java 命令。</p>
<h2 id="配置-JAVA-HOME"><a href="#配置-JAVA-HOME" class="headerlink" title="配置 JAVA_HOME"></a>配置 JAVA_HOME</h2><p>虽然在命令行已经可以直接使用 Java 命令了，但是一些软件依然需要<code>JAVA_HOME</code>的环境变量，在<code>./zshrc</code>中添加如下配置：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">export JAVA_HOME=$(/usr/libexec/java_home)</span><br><span class="line">export PATH=$JAVA_HOME/bin:$PATH</span><br></pre></td></tr></table></figure>

<h1 id="配置环境变量的配置问题"><a href="#配置环境变量的配置问题" class="headerlink" title="配置环境变量的配置问题"></a>配置环境变量的配置问题</h1><p>mac 中用要下载各种工具，然后配置环境变量，拿 gradle 的配置来说，在 <code>.zshrc</code> 中配置其环境变量，<br>之前的配置方式是：</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"># add Gradle_Home</span><br><span class="line">#export GRADLE_HOME=$(/Users/zachaxy/mygradle/gradle-4.1)</span><br><span class="line">export PATH=$PATH:$GRADLE_HOME/bin</span><br></pre></td></tr></table></figure>

<p>然后总是提示 <code>permission denied: /Users/zachaxy/mygradle/gradle-4.1</code>,可是之前 Java 的环境变量就是这样配置的，就没有问题。<br>后来改成如下的方式，就可以了。</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"># add Gradle_Home</span><br><span class="line">export GRADLE_HOME=/Users/zachaxy/mygradle/gradle-4.1</span><br><span class="line">export PATH=$PATH:$GRADLE_HOME/bin</span><br></pre></td></tr></table></figure>

<h1 id="参考"><a href="#参考" class="headerlink" title="参考"></a>参考</h1><p><a href="https://sspai.com/post/41371" target="_blank" rel="noopener">刚从 Windows 转到 macOS，如何快速上手操作</a><br><a href="http://wulfric.me/2015/08/iterm2/" target="_blank" rel="noopener">你应该知道的 iTerm2 使用方法–MAC终端工具</a><br><a href="https://cnbin.github.io/blog/2015/06/20/iterm2-kuai-jie-jian-da-quan/" target="_blank" rel="noopener">iTerm2 快捷键大全</a></p>




    </div>










    <footer class="post-footer">








        <div class="post-eof"></div>

    </footer>
  </div>



  </article>











  <article class="post post-type-normal" itemscope itemtype="http://schema.org/Article">



  <div class="post-block">
    <link itemprop="mainEntityOfPage" href="https://zachaxy.github.io/2017/11/07/卡特兰数简介/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="name" content="zachaxy">
      <meta itemprop="description" content>
      <meta itemprop="image" content="/images/avatar.jpg">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="zachaxy">
    </span>


      <header class="post-header">



          <h2 class="post-title" itemprop="name headline">

                <a class="post-title-link" href="/2017/11/07/卡特兰数简介/" itemprop="url">卡特兰数简介</a></h2>


        <div class="post-meta">
          <span class="post-time">

              <span class="post-meta-item-icon">
                <i class="fa fa-calendar-o"></i>
              </span>

                <span class="post-meta-item-text">发表于</span>

              <time title="创建于" itemprop="dateCreated datePublished" datetime="2017-11-07T09:31:23+08:00">
                2017-11-07
              </time>





          </span>













            <div class="post-wordcount">


                <span class="post-meta-item-icon">
                  <i class="fa fa-file-word-o"></i>
                </span>

                  <span class="post-meta-item-text">字数统计&#58;</span>

                <span title="字数统计">
                  1,154
                </span>





            </div>




        </div>
      </header>





    <div class="post-body" itemprop="articleBody">







            <blockquote>
<p>卡塔兰数是组合数学中一个常在各种计数问题中出现的数列。以比利时的数学家欧仁·查理·卡特兰（1814–1894）命名。</p>
</blockquote>
<h1 id="原理证明"><a href="#原理证明" class="headerlink" title="原理证明"></a>原理证明</h1><p>先假设这样一个场景，有 n 个 1，n 个 -1，那么这 2n 个数字以 <strong>任意顺序</strong> 相加，结果肯定是等于 0 的。但是现在加一个限制，就是在所给的任意顺序的表达式，前 i 项(0&lt;=i&lt;=2n)的和也要&gt;=0,问有多少种组合方式?</p>
<p>首先，如果不加所给的限制，任意排列，那么产生的序列为：C(n,2n)<br>接下来，就要从所有的序列中，排除掉不合法的序列，那么结果就是合法序列数量。</p>
<p>不合法的序列：</p>
<p>想象一下，产生不合法的序列的情形，一定是在前 2i 项相加为 0 后，2i+1 项出现了一个 -1，此序列就是不合法的。同时，2i+2 到 2n 的和为 1。那么我们做一个变换，就是将第 1 项到第 2i+1 项的 -1 全部变为 1,1 全部变为 -1。因为前 2i 项相加为 0，变换后相加依然为 0，但是第 2i+1 变为了 1，这导致前 2i+1 项的和为 1。同时 2i+2 到 2n 的数字没有改变。导致此时整个序列的和变为了 2。</p>
<p>以下是上述的一个例子，第一个式子是不合法的，我们进行一步转换，得到第二个式子。</p>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">1 -1 -1 1 = 0  </span><br><span class="line">-1 1  1 1 = 2</span><br></pre></td></tr></table></figure>

<p>注意，这种转换后和为 2 的式子和为转换前的不合法的式子是一一对应的。也就是说如果出现了不合法的式子，一定能转换成一个唯一的相加为 2 的式子。同理这一步也是可逆的，也就是说如果出现了一个相加为 2 的式子，那么一定有一个不合法的序列和其对应。</p>
<p>前面我们直接找不合法的序列的种类并不好找，但是经过这一步转换后，现在的问题转换为 n+1 个 1，n-1 个 -1 组成相加为 2 的序列种类有多少，那么结果就是：C(n-1,2n)</p>
<p>也就是说，错排种类为：C(n-1,2n)<br>所以合法的种类为：C(n,2n) - C(n-1,2n) = C(n,2n)/(n+1)<br>该结果就是著名的卡特兰公式：f(n) = C(2n, n)/(n+1)</p>
<p>递推公式：f(n) = f(0)<em>f(n-1) + f(1)</em>f(n-2) + f(2)<em>f(n-3) + … + f(n-1)</em>f(0)</p>
<p>f(0)=1，f(1)=1，</p>
<h1 id="使用场景"><a href="#使用场景" class="headerlink" title="使用场景"></a>使用场景</h1><h2 id="出栈顺序-括号匹配"><a href="#出栈顺序-括号匹配" class="headerlink" title="出栈顺序/括号匹配"></a>出栈顺序/括号匹配</h2><p>假设有一个无穷大的栈，现在有 n 个数字按顺序依次进栈，那么合法的进出栈的序列是多少？<br>合法的进出栈，把入栈想象为 1，出栈想象为 -1，那么合法的进出栈序列为：C(n,2n)/(n+1)</p>
<h2 id="排队买票"><a href="#排队买票" class="headerlink" title="排队买票"></a>排队买票</h2><p>假设现在有 2n 个人排队买票，n 个人有 5 块，n 个人有十块，票价正好为 5 块，同时售票员手上没有零钱，那么合法的排队顺序有多少种?<br>这个和之前不一样的是：每个人都是不同的，所以在之前的结果前提下，还要对 n 个人进行排列，结果为：<br>C(n,2n)/(n+1) * n! * n!</p>
<h2 id="二叉查找树种类"><a href="#二叉查找树种类" class="headerlink" title="二叉查找树种类"></a>二叉查找树种类</h2><p>n 个节点(节点序号为 1 ~ n)，将其组成二叉查找树，有几种可能的结果；<br>n = 0，f(0) = 1,认为是空结构；<br>n = 1，f(1) = 1,只有一种可能<br>n = 2, f(2) = 2,分别是 1 作为根节点，2 只能是右子节点；或者 2 作为根节点，1 只能是左子节点；<br>n = 3，f(3) = 5;<br>n = 4, f(4) =<br>……<br>接下来，讨论 n 个节点的情况，每个节点都有可能作为头结点；<br>那么 f(n) = f(0)<em>f(n-1) + f(1)</em>f(n-2) + f(2)<em>f(n-3) + … + f(n-1)</em>f(0)<br>结果其实就是卡特兰数，为  C(n,2n)/(n+1)</p>
<h2 id="排队问题"><a href="#排队问题" class="headerlink" title="排队问题"></a>排队问题</h2><p>12 个高矮不同的人，站成两排，每排 6 人，从左到右，从矮到高；同时第二排的人比第一排的对应的人要高，有几种排列方式；<br>隐藏的卡特兰问题：<br>将 12 个人编号，1~12；站在第一排的为（，站在第二排的人为）；如果出现了不匹配的括号，那么说明不合法；<br> 现在问题变成：任意前缀不能出现）比（多的情况；<br> 结果依然是例题 1 的结果；</p>




    </div>










    <footer class="post-footer">








        <div class="post-eof"></div>

    </footer>
  </div>



  </article>











  <article class="post post-type-normal" itemscope itemtype="http://schema.org/Article">



  <div class="post-block">
    <link itemprop="mainEntityOfPage" href="https://zachaxy.github.io/2017/10/26/groovy入门/">

    <span hidden itemprop="author" itemscope itemtype="http://schema.org/Person">
      <meta itemprop="name" content="zachaxy">
      <meta itemprop="description" content>
      <meta itemprop="image" content="/images/avatar.jpg">
    </span>

    <span hidden itemprop="publisher" itemscope itemtype="http://schema.org/Organization">
      <meta itemprop="name" content="zachaxy">
    </span>


      <header class="post-header">



          <h2 class="post-title" itemprop="name headline">

                <a class="post-title-link" href="/2017/10/26/groovy入门/" itemprop="url">groovy入门</a></h2>


        <div class="post-meta">
          <span class="post-time">

              <span class="post-meta-item-icon">
                <i class="fa fa-calendar-o"></i>
              </span>

                <span class="post-meta-item-text">发表于</span>

              <time title="创建于" itemprop="dateCreated datePublished" datetime="2017-10-26T22:16:20+08:00">
                2017-10-26
              </time>





          </span>













            <div class="post-wordcount">


                <span class="post-meta-item-icon">
                  <i class="fa fa-file-word-o"></i>
                </span>

                  <span class="post-meta-item-text">字数统计&#58;</span>

                <span title="字数统计">
                  1,604
                </span>





            </div>




        </div>
      </header>





    <div class="post-body" itemprop="articleBody">







            <h1 id="变量定义"><a href="#变量定义" class="headerlink" title="变量定义"></a>变量定义</h1><p>groovy 是动态类型的语言，也就是说不需要指定变量的类型，类型是可以值来推导的。</p>
<ul>
<li>不指定类型定义变量： <code>i = 10</code></li>
<li>使用关键字`` def<code>，虽不是必须的，但是为了代码清晰，还是建议使用 def 关键字定义变量</code>def i = 10`</li>
</ul>
<p>这里有个误区：def 关键字的出现时替代变量类型的占位符，如果你已经明确了变量的类型，就没必要使用 def，也就是说 <code>def int i = 10</code> 是没有必要的</p>
<h1 id="字符串"><a href="#字符串" class="headerlink" title="字符串"></a>字符串</h1><ul>
<li>单引号:单引号中的内容严格对应 Java 中的 String</li>
<li>双引号:和脚本语言类似，如果字符串中有$符的话，先对 $表达式进行求值</li>
<li>三引号:针对的是很长的字符串，只要在三引号之间，可以随意换行</li>
</ul>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">def</span> s1 = <span class="string">'hello'</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">def</span> s2 = <span class="string">"string append $&#123;version + 1&#125;"</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">def</span> s3 = <span class="string">'''随意</span></span><br><span class="line"><span class="string">换行</span></span><br><span class="line"><span class="string">打印</span></span><br><span class="line"><span class="string">'''</span></span><br></pre></td></tr></table></figure>

<p>字符串的长度：<code>s1.size()</code></p>
<p>字符串的访问：<code>s1[2]</code>   //被当做数组来处理；</p>
<p>或者  <code>s1.getAt(index)</code></p>
<p>字符串的重复：</p>
<p><code>s = s1*3</code>  // 代表是将 s1 拼接三次</p>
<h1 id="函数定义"><a href="#函数定义" class="headerlink" title="函数定义"></a>函数定义</h1><ul>
<li>参数可以不指定类型</li>
<li>方法体中可以不使用 return 来返回，这样默认的返回值就是最后一行语句的值，但是如果不指定 return，定义函数时必须要使用 def。</li>
<li>可以指明返回值类型,这样就可以省略 def 关键字；但是如果未指定返回值类型，那么定义函数时必须使用 def 关键字</li>
<li>默认参数：可以给参数定义默认值，但是要注意的是，如果要定义有默认值的参数，那么该参数必须在参数列表的末尾</li>
</ul>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">int</span> sum(<span class="keyword">int</span> a,<span class="keyword">int</span> b = <span class="number">0</span>)&#123;</span><br><span class="line">	<span class="keyword">return</span> a + b;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line">sum(<span class="number">1</span>,<span class="number">2</span>)</span><br><span class="line">sum(<span class="number">1</span>)</span><br></pre></td></tr></table></figure>

<h1 id="函数调用"><a href="#函数调用" class="headerlink" title="函数调用"></a>函数调用</h1><ul>
<li>调用时，可以不加括号，但这并不是一个好的习惯，因为如果一个函数是无参的，那么不带括号，很可能被误认为是属性的调用；同时在嵌套函数调用时，也容易出错（将参数设置为另一个方法调用的结果）</li>
<li>最好的一种形式是：能加括号都加括号；如果该方法只有一个参数，那么调用时加括号，如果有多个参数，则可以省略括号</li>
<li>特别注意：如果该函数没有参数，那么调用时，必须加括号；同时这个的参数个数要和闭包的参数个数区分开</li>
</ul>
<h1 id="Groovy-bean-对象"><a href="#Groovy-bean-对象" class="headerlink" title="Groovy bean 对象"></a>Groovy bean 对象</h1><figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span>  <span class="title">Bean</span>&#123;</span></span><br><span class="line">    <span class="keyword">int</span> version</span><br><span class="line">    String name;</span><br><span class="line"></span><br><span class="line">    Bean(<span class="keyword">int</span> version,String name)&#123;</span><br><span class="line">        <span class="keyword">this</span>.version = version;</span><br><span class="line">        <span class="keyword">this</span>.name = name;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line">Bean bean1 = <span class="keyword">new</span> Bean(<span class="number">1</span>,<span class="string">"zx"</span>)</span><br><span class="line"></span><br><span class="line">println bean1.name</span><br></pre></td></tr></table></figure>

<p>上面定义的 Bean 对象，在其内部定义了两个成员变量 version 和 name，这样默认就会为我们生成其对应的 getter 和 setter 方法。而在外部访问该成员变量时，其实是调用对应的 getter 和 setter 方法。</p>
<h1 id="闭包"><a href="#闭包" class="headerlink" title="闭包"></a>闭包</h1><p>闭包和函数是类似的，是一个代码片段，可以定义一个引用指向这个闭包，这类似于 C 语言中的函数指针；</p>
<p>闭包还可以获取外部变量；与 Java 中的内部类不同的是，在闭包内不仅可以获取到外部变量，同时也可以将其修改，修改对外部是可见的。</p>
<p>与函数定义不同的是，闭包的参数是在方法体内定义的，以 -&gt; 分割，左侧为参数，右侧为方法体</p>
<p>闭包方法体内，最后一句为返回值。</p>
<p>闭包的默认参数：如果定义的闭包只有一个参数，那么可以在闭包内直接写方法体，使用 <code>$it</code> 来获取参数。</p>
<p>如果要定义一个没有参数的闭包，那么闭包内， -&gt; 左侧为空，则代表该闭包没有参数</p>
<p>Groovy 中的函数，可以用闭包作为参数；</p>
<h1 id="集合类"><a href="#集合类" class="headerlink" title="集合类"></a>集合类</h1><p>groovy 中的集合包含两种：list 和 map，其使用也很简单</p>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">list = [<span class="number">0</span>,<span class="number">1</span>,<span class="number">2</span>]</span><br><span class="line">list &lt;&lt; <span class="number">3</span></span><br><span class="line">println list.size();</span><br><span class="line"></span><br><span class="line">map = [<span class="string">name:</span><span class="string">"zx"</span>,<span class="string">age:</span><span class="number">25</span>];</span><br><span class="line">map.merry = <span class="literal">false</span>	<span class="comment">// 向 map 添加键值对</span></span><br><span class="line">println map.size()  <span class="comment">// 3</span></span><br></pre></td></tr></table></figure>

<h1 id="运算符"><a href="#运算符" class="headerlink" title="运算符"></a>运算符</h1><ul>
<li>范围运算符(..)</li>
</ul>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//range 更像是一个数组，其长度为 6，其为从 5 到 10</span></span><br><span class="line"><span class="keyword">def</span> range = <span class="number">5.</span><span class="number">.10</span></span><br><span class="line"><span class="comment">//通过 get(index)来获取对应的值</span></span><br><span class="line">println range.get(<span class="number">2</span>)</span><br><span class="line"></span><br><span class="line"><span class="comment">// 其它实例</span></span><br><span class="line"><span class="number">1</span> .. &lt;<span class="number">10</span>    <span class="comment">//  独占范围的示例</span></span><br><span class="line"><span class="string">'a'</span>..<span class="string">'x'</span>   <span class="comment">// 范围也可以由字符组成</span></span><br><span class="line"><span class="number">10.</span><span class="number">.1</span>     <span class="comment">// 范围也可以按降序排列</span></span><br><span class="line"><span class="string">'x'</span>..<span class="string">'a'</span> <span class="comment">// 范围也可以由字符组成并按降序排列。</span></span><br><span class="line"></span><br><span class="line"><span class="comment">// 由此就有如下 foreach 的写法</span></span><br><span class="line"><span class="keyword">for</span>(<span class="keyword">int</span> i <span class="keyword">in</span> <span class="number">1.</span><span class="number">.5</span>) &#123;</span><br><span class="line">	println(i);</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<ul>
<li>三目运算符(?:)</li>
</ul>
<figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">// 假设有这样一个需求，如果 name 不为 null，那么就输出 name 的值，否则输出 Anonymous</span><br><span class="line">// 下面的三目运算符的写法，未免有些啰嗦</span><br><span class="line">displayName = name ? name : &apos;Anonymous&apos;</span><br><span class="line"></span><br><span class="line">// 下面是 groovy 中支持三目运算符的写法</span><br><span class="line">displayName = name ?: &apos;Anonymous&apos;</span><br></pre></td></tr></table></figure>

<ul>
<li>展开操作符(*.)</li>
</ul>
<p>应用于实现了 iterator 的对象中，一般是数组，集合，是 foreach 的缩写</p>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">def</span> technologies = [<span class="string">'Groovy'</span>,<span class="string">'Grails'</span>,<span class="string">'Gradle'</span>]</span><br><span class="line">technologies*.toUpperCase() <span class="comment">// = to technologies.collect &#123; it?.toUpperCase() &#125;</span></span><br></pre></td></tr></table></figure>

<ul>
<li>安全操作符(?.)</li>
</ul>
<p>可以有效的避免空指针</p>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// eg：get(1)返回的结果是 null，此时如果调用 user.username 会产生空指针异常</span></span><br><span class="line"><span class="comment">//而是用 ?. 如果 user 为空,那么 username 也为 空，不会产生空指针异常</span></span><br><span class="line"><span class="keyword">def</span> user = User.get(<span class="number">1</span>)</span><br><span class="line"><span class="keyword">def</span> username = user?.username</span><br></pre></td></tr></table></figure>

<h1 id="文件操作"><a href="#文件操作" class="headerlink" title="文件操作"></a>文件操作</h1><p>groovy 提供了比 Java 更为便捷的方法来操作文件，其<a href="http://www.groovy-lang.org/gdk.html" target="_blank" rel="noopener">API 文档参考</a></p>
<figure class="highlight groovy"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br></pre></td><td class="code"><pre><span class="line">File file = <span class="keyword">new</span> File(<span class="string">"E:/hello.txt"</span>)</span><br><span class="line"><span class="comment">//按行读文件 </span></span><br><span class="line">file.eachLine &#123;  </span><br><span class="line">   line -&gt; println <span class="string">"line : $line"</span>; </span><br><span class="line">&#125; </span><br><span class="line"></span><br><span class="line"><span class="comment">//读取文件的整个内容，是用 text 熟悉</span></span><br><span class="line">println  file.text</span><br><span class="line"></span><br><span class="line"><span class="comment">//获取文件内同的大小，单位是字节</span></span><br><span class="line">println file.length()</span><br><span class="line"></span><br><span class="line"><span class="comment">// 写入文件,内容为 hello world</span></span><br><span class="line">file.withWriter(<span class="string">'utf-8'</span>) &#123; </span><br><span class="line">	writer -&gt; writer.writeLine <span class="string">'Hello World'</span> </span><br><span class="line">&#125;  </span><br><span class="line"></span><br><span class="line"><span class="comment">//复制文件</span></span><br><span class="line"><span class="keyword">def</span> src = <span class="keyword">new</span> File(<span class="string">"E:/hello.txt"</span>)</span><br><span class="line"><span class="keyword">def</span> dst = <span class="keyword">new</span> File(<span class="string">"E:/hello1.txt"</span>)</span><br><span class="line">dst &lt;&lt; src.text</span><br><span class="line"></span><br><span class="line"><span class="comment">//递归显示目录及其子目录中的所有文件</span></span><br><span class="line">file.eachFileRecurse() &#123;</span><br><span class="line">	file -&gt; println file.getAbsolutePath()</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>

<h1 id="参考"><a href="#参考" class="headerlink" title="参考"></a>参考</h1><p><a href="http://groovy-lang.org/documentation.html" target="_blank" rel="noopener">官方手册</a><br><a href="https://learnxinyminutes.com/docs/groovy/" target="_blank" rel="noopener">Learn groovy in Y minutes</a><br><a href="http://www.jianshu.com/p/ba55dc163dfd" target="_blank" rel="noopener">使用 Groovy 开发之新特性</a><br><a href="http://blog.csdn.net/dabaoonline/article/details/50477090" target="_blank" rel="noopener">日积月累–Groovy 语言规范之操作符</a><br><a href="http://www.jianshu.com/p/2c17a50ff7f1" target="_blank" rel="noopener">Groovy 学习之-运行时元编程</a><br><a href="https://www.ibm.com/developerworks/cn/education/java/j-groovy/j-groovy.html#N1036D" target="_blank" rel="noopener">精通 Groovy</a></p>




    </div>










    <footer class="post-footer">








        <div class="post-eof"></div>

    </footer>
  </div>



  </article>



  </section>


  <nav class="pagination">
    <a class="extend prev" rel="prev" href="/page/5/"><i class="fa fa-angle-left"></i></a><a class="page-number" href="/">1</a><span class="space">&hellip;</span><a class="page-number" href="/page/5/">5</a><span class="page-number current">6</span><a class="page-number" href="/page/7/">7</a><span class="space">&hellip;</span><a class="page-number" href="/page/13/">13</a><a class="extend next" rel="next" href="/page/7/"><i class="fa fa-angle-right"></i></a>
  </nav>



          </div>





        </div>



  <div class="sidebar-toggle">
    <div class="sidebar-toggle-line-wrap">
      <span class="sidebar-toggle-line sidebar-toggle-line-first"></span>
      <span class="sidebar-toggle-line sidebar-toggle-line-middle"></span>
      <span class="sidebar-toggle-line sidebar-toggle-line-last"></span>
    </div>
  </div>

  <aside id="sidebar" class="sidebar">

      <div id="sidebar-dimmer"></div>

    <div class="sidebar-inner">





      <section class="site-overview-wrap sidebar-panel sidebar-panel-active">
        <div class="site-overview">
          <div class="site-author motion-element" itemprop="author" itemscope itemtype="http://schema.org/Person">

              <img class="site-author-image" itemprop="image" src="/images/avatar.jpg" alt="zachaxy">

              <p class="site-author-name" itemprop="name">zachaxy</p>
              <p class="site-description motion-element" itemprop="description"></p>
          </div>

          <nav class="site-state motion-element">


              <div class="site-state-item site-state-posts">

                <a href="/archives">

                  <span class="site-state-item-count">64</span>
                  <span class="site-state-item-name">日志</span>
                </a>
              </div>







              <div class="site-state-item site-state-tags">
                <a href="/tags/index.html">
                  <span class="site-state-item-count">12</span>
                  <span class="site-state-item-name">标签</span>
                </a>
              </div>


          </nav>



          <div class="links-of-author motion-element">


                <span class="links-of-author-item">
                  <a href="https://github.com/zachaxy" target="_blank" title="GitHub">

                      <i class="fa fa-fw fa-globe"></i>GitHub</a>
                </span>

                <span class="links-of-author-item">
                  <a href="https://weibo.com/3242765540" target="_blank" title="Weibo">

                      <i class="fa fa-fw fa-globe"></i>Weibo</a>
                </span>


          </div>









        </div>
      </section>





    </div>
  </aside>



      </div>
    </main>

    <footer id="footer" class="footer">
      <div class="footer-inner">
        <div class="copyright">&copy; <span itemprop="copyrightYear">2020</span>
  <span class="with-love">
    <i class="fa fa-user"></i>
  </span>
  <span class="author" itemprop="copyrightHolder">zachaxy</span>


    <span class="post-meta-divider">|</span>
    <span class="post-meta-item-icon">
      <i class="fa fa-area-chart"></i>
    </span>

      <span class="post-meta-item-text">站点文章字数总计&#58;</span>

    <span title="站点文章字数总计">147.9k</span>

</div>






  <div class="theme-info">主题 &mdash; <a class="theme-link" target="_blank" href="https://github.com/iissnan/hexo-theme-next">NexT.Muse</a></div>













      </div>
    </footer>


      <div class="back-to-top">
        <i class="fa fa-arrow-up"></i>

          <span id="scrollpercent"><span>0</span>%</span>

      </div>




  </div>



<script type="text/javascript">
  if (Object.prototype.toString.call(window.Promise) !== '[object Function]') {
    window.Promise = null;
  }
</script>
























    <script type="text/javascript" src="/lib/jquery/index.js?v=2.1.3"></script>




    <script type="text/javascript" src="/lib/fastclick/lib/fastclick.min.js?v=1.0.6"></script>




    <script type="text/javascript" src="/lib/jquery_lazyload/jquery.lazyload.js?v=1.9.7"></script>




    <script type="text/javascript" src="/lib/velocity/velocity.min.js?v=1.2.1"></script>




    <script type="text/javascript" src="/lib/velocity/velocity.ui.min.js?v=1.2.1"></script>




    <script type="text/javascript" src="/lib/fancybox/source/jquery.fancybox.pack.js?v=2.1.5"></script>






  <script type="text/javascript" src="/js/src/utils.js?v=5.1.3"></script>

  <script type="text/javascript" src="/js/src/motion.js?v=5.1.3"></script>











  <script type="text/javascript" src="/js/src/bootstrap.js?v=5.1.3"></script>







































  <script type="text/javascript">
    // Popup Window;
    var isfetched = false;
    var isXml = true;
    // Search DB path;
    var search_path = "search.xml";
    if (search_path.length === 0) {
      search_path = "search.xml";
    } else if (/json$/i.test(search_path)) {
      isXml = false;
    }
    var path = "/" + search_path;
    // monitor main search box;

    var onPopupClose = function (e) {
      $('.popup').hide();
      $('#local-search-input').val('');
      $('.search-result-list').remove();
      $('#no-result').remove();
      $(".local-search-pop-overlay").remove();
      $('body').css('overflow', '');
    }

    function proceedsearch() {
      $("body")
        .append('<div class="search-popup-overlay local-search-pop-overlay"></div>')
        .css('overflow', 'hidden');
      $('.search-popup-overlay').click(onPopupClose);
      $('.popup').toggle();
      var $localSearchInput = $('#local-search-input');
      $localSearchInput.attr("autocapitalize", "none");
      $localSearchInput.attr("autocorrect", "off");
      $localSearchInput.focus();
    }

    // search function;
    var searchFunc = function(path, search_id, content_id) {
      'use strict';

      // start loading animation
      $("body")
        .append('<div class="search-popup-overlay local-search-pop-overlay">' +
          '<div id="search-loading-icon">' +
          '<i class="fa fa-spinner fa-pulse fa-5x fa-fw"></i>' +
          '</div>' +
          '</div>')
        .css('overflow', 'hidden');
      $("#search-loading-icon").css('margin', '20% auto 0 auto').css('text-align', 'center');

      $.ajax({
        url: path,
        dataType: isXml ? "xml" : "json",
        async: true,
        success: function(res) {
          // get the contents from search data
          isfetched = true;
          $('.popup').detach().appendTo('.header-inner');
          var datas = isXml ? $("entry", res).map(function() {
            return {
              title: $("title", this).text(),
              content: $("content",this).text(),
              url: $("url" , this).text()
            };
          }).get() : res;
          var input = document.getElementById(search_id);
          var resultContent = document.getElementById(content_id);
          var inputEventFunction = function() {
            var searchText = input.value.trim().toLowerCase();
            var keywords = searchText.split(/[\s\-]+/);
            if (keywords.length > 1) {
              keywords.push(searchText);
            }
            var resultItems = [];
            if (searchText.length > 0) {
              // perform local searching
              datas.forEach(function(data) {
                var isMatch = false;
                var hitCount = 0;
                var searchTextCount = 0;
                var title = data.title.trim();
                var titleInLowerCase = title.toLowerCase();
                var content = data.content.trim().replace(/<[^>]+>/g,"");
                var contentInLowerCase = content.toLowerCase();
                var articleUrl = decodeURIComponent(data.url);
                var indexOfTitle = [];
                var indexOfContent = [];
                // only match articles with not empty titles
                if(title != '') {
                  keywords.forEach(function(keyword) {
                    function getIndexByWord(word, text, caseSensitive) {
                      var wordLen = word.length;
                      if (wordLen === 0) {
                        return [];
                      }
                      var startPosition = 0, position = [], index = [];
                      if (!caseSensitive) {
                        text = text.toLowerCase();
                        word = word.toLowerCase();
                      }
                      while ((position = text.indexOf(word, startPosition)) > -1) {
                        index.push({position: position, word: word});
                        startPosition = position + wordLen;
                      }
                      return index;
                    }

                    indexOfTitle = indexOfTitle.concat(getIndexByWord(keyword, titleInLowerCase, false));
                    indexOfContent = indexOfContent.concat(getIndexByWord(keyword, contentInLowerCase, false));
                  });
                  if (indexOfTitle.length > 0 || indexOfContent.length > 0) {
                    isMatch = true;
                    hitCount = indexOfTitle.length + indexOfContent.length;
                  }
                }

                // show search results

                if (isMatch) {
                  // sort index by position of keyword

                  [indexOfTitle, indexOfContent].forEach(function (index) {
                    index.sort(function (itemLeft, itemRight) {
                      if (itemRight.position !== itemLeft.position) {
                        return itemRight.position - itemLeft.position;
                      } else {
                        return itemLeft.word.length - itemRight.word.length;
                      }
                    });
                  });

                  // merge hits into slices

                  function mergeIntoSlice(text, start, end, index) {
                    var item = index[index.length - 1];
                    var position = item.position;
                    var word = item.word;
                    var hits = [];
                    var searchTextCountInSlice = 0;
                    while (position + word.length <= end && index.length != 0) {
                      if (word === searchText) {
                        searchTextCountInSlice++;
                      }
                      hits.push({position: position, length: word.length});
                      var wordEnd = position + word.length;

                      // move to next position of hit

                      index.pop();
                      while (index.length != 0) {
                        item = index[index.length - 1];
                        position = item.position;
                        word = item.word;
                        if (wordEnd > position) {
                          index.pop();
                        } else {
                          break;
                        }
                      }
                    }
                    searchTextCount += searchTextCountInSlice;
                    return {
                      hits: hits,
                      start: start,
                      end: end,
                      searchTextCount: searchTextCountInSlice
                    };
                  }

                  var slicesOfTitle = [];
                  if (indexOfTitle.length != 0) {
                    slicesOfTitle.push(mergeIntoSlice(title, 0, title.length, indexOfTitle));
                  }

                  var slicesOfContent = [];
                  while (indexOfContent.length != 0) {
                    var item = indexOfContent[indexOfContent.length - 1];
                    var position = item.position;
                    var word = item.word;
                    // cut out 100 characters
                    var start = position - 20;
                    var end = position + 80;
                    if(start < 0){
                      start = 0;
                    }
                    if (end < position + word.length) {
                      end = position + word.length;
                    }
                    if(end > content.length){
                      end = content.length;
                    }
                    slicesOfContent.push(mergeIntoSlice(content, start, end, indexOfContent));
                  }

                  // sort slices in content by search text's count and hits' count

                  slicesOfContent.sort(function (sliceLeft, sliceRight) {
                    if (sliceLeft.searchTextCount !== sliceRight.searchTextCount) {
                      return sliceRight.searchTextCount - sliceLeft.searchTextCount;
                    } else if (sliceLeft.hits.length !== sliceRight.hits.length) {
                      return sliceRight.hits.length - sliceLeft.hits.length;
                    } else {
                      return sliceLeft.start - sliceRight.start;
                    }
                  });

                  // select top N slices in content

                  var upperBound = parseInt('1');
                  if (upperBound >= 0) {
                    slicesOfContent = slicesOfContent.slice(0, upperBound);
                  }

                  // highlight title and content

                  function highlightKeyword(text, slice) {
                    var result = '';
                    var prevEnd = slice.start;
                    slice.hits.forEach(function (hit) {
                      result += text.substring(prevEnd, hit.position);
                      var end = hit.position + hit.length;
                      result += '<b class="search-keyword">' + text.substring(hit.position, end) + '</b>';
                      prevEnd = end;
                    });
                    result += text.substring(prevEnd, slice.end);
                    return result;
                  }

                  var resultItem = '';

                  if (slicesOfTitle.length != 0) {
                    resultItem += "<li><a href='" + articleUrl + "' class='search-result-title'>" + highlightKeyword(title, slicesOfTitle[0]) + "</a>";
                  } else {
                    resultItem += "<li><a href='" + articleUrl + "' class='search-result-title'>" + title + "</a>";
                  }

                  slicesOfContent.forEach(function (slice) {
                    resultItem += "<a href='" + articleUrl + "'>" +
                      "<p class=\"search-result\">" + highlightKeyword(content, slice) +
                      "...</p>" + "</a>";
                  });

                  resultItem += "</li>";
                  resultItems.push({
                    item: resultItem,
                    searchTextCount: searchTextCount,
                    hitCount: hitCount,
                    id: resultItems.length
                  });
                }
              })
            };
            if (keywords.length === 1 && keywords[0] === "") {
              resultContent.innerHTML = '<div id="no-result"><i class="fa fa-search fa-5x" /></div>'
            } else if (resultItems.length === 0) {
              resultContent.innerHTML = '<div id="no-result"><i class="fa fa-frown-o fa-5x" /></div>'
            } else {
              resultItems.sort(function (resultLeft, resultRight) {
                if (resultLeft.searchTextCount !== resultRight.searchTextCount) {
                  return resultRight.searchTextCount - resultLeft.searchTextCount;
                } else if (resultLeft.hitCount !== resultRight.hitCount) {
                  return resultRight.hitCount - resultLeft.hitCount;
                } else {
                  return resultRight.id - resultLeft.id;
                }
              });
              var searchResultList = '<ul class=\"search-result-list\">';
              resultItems.forEach(function (result) {
                searchResultList += result.item;
              })
              searchResultList += "</ul>";
              resultContent.innerHTML = searchResultList;
            }
          }

          if ('auto' === 'auto') {
            input.addEventListener('input', inputEventFunction);
          } else {
            $('.search-icon').click(inputEventFunction);
            input.addEventListener('keypress', function (event) {
              if (event.keyCode === 13) {
                inputEventFunction();
              }
            });
          }

          // remove loading animation
          $(".local-search-pop-overlay").remove();
          $('body').css('overflow', '');

          proceedsearch();
        }
      });
    }

    // handle and trigger popup window;
    $('.popup-trigger').click(function(e) {
      e.stopPropagation();
      if (isfetched === false) {
        searchFunc(path, 'local-search-input', 'local-search-result');
      } else {
        proceedsearch();
      };
    });

    $('.popup-btn-close').click(onPopupClose);
    $('.popup').click(function(e){
      e.stopPropagation();
    });
    $(document).on('keyup', function (event) {
      var shouldDismissSearchPopup = event.which === 27 &&
        $('.search-popup').is(':visible');
      if (shouldDismissSearchPopup) {
        onPopupClose();
      }
    });
  </script>

















  <script type="text/javascript" src="/js/src/js.cookie.js?v=5.1.3"></script>
  <script type="text/javascript" src="/js/src/scroll-cookie.js?v=5.1.3"></script>





</body>
</html>
